package com.powerfl.frm.taf{
	
	import away3d.animators.*;
	
	import flash.filters.*;

	final internal class TAFawayVar{
		
		public var x:Number;
		public var _x:int;
		public var y:Number;
		public var _y:int;
		public var z:Number;
		public var _z:int;
		
		public var rotationX:Number;
		public var _rotationX:int;
		public var rotationY:Number;
		public var _rotationY:int;
		public var rotationZ:Number;
		public var _rotationZ:int;

		public var scaleX:Number;
		public var _scaleX:int;
		public var scaleY:Number;
		public var _scaleY:int;
		public var scaleZ:Number;
		public var _scaleZ:int;
		
		public var _autoSize:int;
		public var width:Number;
		public var _width:int;
		public var height:Number;
		public var _height:int;
		public var depth:Number;
		public var _depth:int;
		public var segmentsW:int;
		public var _segmentsW:int;
		public var segmentsH:int;
		public var _segmentsH:int;
	
		public var pushback:Boolean;
		public var _pushback:int;
		public var pushfront:Boolean;
		public var _pushfront:int;
		public var ownCanvas:Boolean;
		public var _ownCanvas:int;
		public var ownLights:Boolean;
		public var _ownLights:int;
		public var visible:Boolean;
		public var _visible:int;
		public var useHandCursor:Boolean;
		public var _useHandCursor:int;
		
		public var bothsides:Boolean;
		public var _bothsides:int;
		public var mouseEnabled:Boolean;
		public var _mouseEnabled:int;
		
		public var alpha:Number;
		public var _alpha:int;
		public var blendMode:String;
		public var _blendMode:int;
		
		public var material:Array = [];
		public var _material:int;
		public var back:Array = [];
		public var _back:int;
		public var materialLibrary:Object = {};
		public var _materialLibrary:int;
		
		public var shading:Boolean;
		public var _shading:int;
		public var centerMeshes:Boolean;
		public var _centerMeshes:int;
		
		public var _blur:int;
		public var _blurRemove:int;
		public var blurX:Number;
		public var blurY:Number;
		public var blurQ:int;
		
		public var _glow:int;
		public var _glowRemove:int;
		public var glowX:Number;
		public var glowY:Number;
		public var glowQ:int;
		public var glowS:Number;
		public var glowA:Number;
		public var glowC:uint;
		
		public var _drop:int;
		public var _dropRemove:int;
		public var dropC:uint;
		public var dropX:Number;
		public var dropY:Number;
		public var dropQ:int;
		public var dropAN:Number;
		public var dropA:Number;
		public var dropD:Number;
		//bitmapBlit전용--------------------------------------------------------------------------------------------------------------------
		public var _tx:int;
		public var tx:Number;
		public var _ty:int;
		public var ty:Number;
		//지연실행--------------------------------------------------------------------------------------------------------------------
		public var _delayed:int;
		public var delayed:Object;
		//Sprite3D전용--------------------------------------------------------------------------------------------------------------------
		public var rotation:Number;
		public var _rotation:int;
		public var scaling:Number;
		public var _scaling:int;
		//트위닝전용--------------------------------------------------------------------------------------------------------------------
		public var ease:Function;
		public var init:TAFawayVar;
		public var object:*;
		
		private var _blurFilter:BlurFilter;
		private var _glowFilter:GlowFilter;
		private var _dropFilter:DropShadowFilter;
		
		public function TAFawayVar(){}
		internal function collect():TAFawayVar{
			_x = _y = _z = 0;
			_rotationX = _rotationY = _rotationZ =  0;
			_scaleX = _scaleY = _scaleZ = 0;
			_autoSize = _width = _height = _depth = _segmentsW = _segmentsH = 0;
			_useHandCursor = _ownCanvas = _ownLights = _visible = _bothsides = _mouseEnabled = 0;
			_alpha = _blendMode = 0;
			_pushback = _pushfront = 0;
			
			material.length = 0;
			back.length = 0;
			materialLibrary = {};
			
			_material = _back = _materialLibrary = 0;
			
			_centerMeshes = _shading = 0;
			
			_blur = _blurRemove = _glow = _glowRemove = _drop = _dropRemove = 0;
			
			_delayed = 0;
			delayed = null; 
			
			_rotation = _scaling = 0;
			
			_tx = _ty = 0;
			
			ease = null;
			init = null;
			object = null;
			
			return this;
		}
		internal function delayAdd( $key:String, $value:String ):void{
			if( delayed ){}else{
				delayed = {};
			}
			_delayed = -1;
			delayed[$key] = $value;
		} 
		internal function delay( $object:* = null ):void{
			var key:*;
			if( _delayed < 0 ){
				for( key in delayed ){
					this['_'+key] = -1;
					this[key] = TAF.EXPRESSION( delayed[key], $object );
				}
			}
		}
		internal function materialCheck():TAFawayVar{
			if( _material || _back || _materialLibrary ){}else{
				TAF.SELF.error( 'material 또는 back 중에 하나는 반드시 정의되어야 합니다.' );
			}
			return this;
		}
		internal function applyTween( $rate:Number ):void{
			var isFilter:int;
			if( _tx < 0 ){
				object.tx = ease( init.tx, tx, $rate );
			}
			if( _ty < 0 ){
				object.ty = ease( init.ty, ty, $rate );
			}
			if( _x < 0 ){
				object.x = ease( init.x, x, $rate );
				if( object is TAFbitmapBlitChild ){
					object.x;
				} 
			}
			if( _y < 0 ){
				object.y = ease( init.y, y, $rate );
			}
			if( _z < 0 ){
				object.z = ease( init.z, z, $rate );
			}
			if( _rotationX < 0 ){
				object.rotationX = ease( init.rotationX, rotationX, $rate );
			}
			if( _rotationY < 0 ){
				object.rotationY = ease( init.rotationY, rotationY, $rate );
			}
			if( _rotationZ < 0 ){
				object.rotationZ = ease( init.rotationZ, rotationZ, $rate );
			}
			if( _rotation < 0 ){
				object.rotation = ease( init.rotation, rotation, $rate );
			}
			if( _scaling < 0 ){
				object.scaling = ease( init.scaling, scaling, $rate );
			}
			if( _scaleX < 0 ){
				object.scaleX = ease( init.scaleX, scaleX, $rate );
			}
			if( _scaleY < 0 ){
				object.scaleY = ease( init.scaleY, scaleY, $rate );
			}
			if( _scaleZ < 0 ){
				object.scaleZ = ease( init.scaleZ, scaleZ, $rate );
			}
			if( _width < 0 ){
				object.width = ease( init.width, width, $rate );
			}
			if( _height < 0 ){
				object.height = ease( init.height, height, $rate );
			}
			if( _depth < 0 ){
				object.depth = ease( init.depth, depth, $rate );
			}
			if( _segmentsW < 0 ){
				object.segmentsW = ease( init.segmentsW, segmentsW, $rate );
			}
			if( _segmentsH < 0 ){
				object.segmentsH = ease( init.segmentsH, segmentsH, $rate );
			}
			if( _depth < 0 ){
				object.depth = ease( init.depth, depth, $rate );
			}
			if( _alpha < 0 ){
				object.alpha = ease( init.alpha, alpha, $rate );
			}
			if( _blur < 0 ){
				if( _blurFilter ){}else{
					_blurFilter = filterSet( object, 'blur' );
				}
				_blurFilter.blurX = ease( init.blurX, blurX, $rate );
				_blurFilter.blurY = ease( init.blurY, blurY, $rate );
				_blurFilter.quality = ease( init.blurQ, blurQ, $rate );
				isFilter = -1;
			}
			if( _glow < 0 ){
				if( _glowFilter ){}else{
					_glowFilter = filterSet( object, 'glow' );
				}
				_glowFilter.blurX = ease( init.glowX, glowX, $rate );
				_glowFilter.blurY = ease( init.glowY, glowY, $rate );
				_glowFilter.quality = ease( init.glowQ, glowQ, $rate );
				_glowFilter.strength = ease( init.glowS, glowS, $rate );
				_glowFilter.alpha = ease( init.glowA, glowA, $rate );
				_glowFilter.color = ease( init.glowC, glowC, $rate );
				isFilter = -1;
			}
			if( _drop < 0 ){
				if( _dropFilter ){}else{
					_dropFilter = filterSet( object, 'drop' );
				}
				_dropFilter.color = ease( init.dropC, dropC, $rate );
				_dropFilter.blurX = ease( init.dropX, dropX, $rate );
				_dropFilter.blurY = ease( init.dropY, dropY, $rate );
				_dropFilter.quality = ease( init.dropQ, dropQ, $rate );
				_dropFilter.angle = ease( init.dropAN, dropAN, $rate );
				_dropFilter.alpha = ease( init.dropA, dropA, $rate );
				_dropFilter.distance = ease( init.dropD, dropD, $rate );
				isFilter = -1;
			}
			if( isFilter < 0 ){
				object.filters = TAF.SELF._treeFilter[object];
			}
		}
		internal function apply( $target:* ):void{
			var isFilter:int, temp:*, key:*;
			delay( $target );
			if( _ownCanvas < 0 ){
				if( 'ownCanvas' in $target ){ 
					$target.ownCanvas = ownCanvas;
				}
			}
			if( _ownLights < 0 ){
				$target.ownLights = ownLights;
			}
			if( _pushback < 0 ){
				$target.pushback = pushback;
			}
			if( _pushfront < 0 ){
				$target.pushfront = pushfront;
			}
			if( _tx < 0 ){
				$target.tx = tx;
			}
			if( _ty < 0 ){
				$target.ty = ty;
			}
			if( _x < 0 ){
				$target.x = x;
			}
			if( _y < 0 ){
				$target.y = y;
			}
			if( _z < 0 ){
				$target.z = z;
			}
			if( _rotationX < 0 ){
				$target.rotationX = rotationX;
			}
			if( _rotationY < 0 ){
				$target.rotationY = rotationY;
			}
			if( _rotationZ < 0 ){
				$target.rotationZ = rotationZ;
			}
			if( _rotation < 0 ){
				$target.rotation = rotation;
			}
			if( _scaling < 0 ){
				$target.scaling = scaling;
			}
			if( _scaleX < 0 ){
				$target.scaleX = scaleX;
			}
			if( _scaleY < 0 ){
				$target.scaleY = scaleY;
			}
			if( _scaleZ < 0 ){
				$target.scaleZ = scaleZ;
			}
			if( _width < 0 ){
				if( '_width' in $target ){
					$target._width = width;
				}else{
					$target.width = width;
				}
			}
			if( _height < 0 ){
				if( '_height' in $target ){
					$target._height = height;
				}else{
					$target.height = height;
				}
			}
			if( _depth < 0 ){
				$target.depth = depth;
			}
			if( _segmentsW < 0 ){
				$target.segmentsW = segmentsW;
			}
			if( _segmentsH < 0 ){
				$target.segmentsH = segmentsH;
			}
			if( _useHandCursor < 0 ){
				$target.useHandCursor = useHandCursor;
			}
			if( _visible < 0 ){
				$target.visible = visible;
			}
			if( _depth < 0 ){
				$target.depth = depth;
			}
			if( _bothsides < 0 ){
				$target.bothsides = bothsides;
			}
			if( _mouseEnabled < 0 ){
				$target.mouseEnabled = mouseEnabled;
			}
			if( _alpha < 0 ){
				$target.alpha = alpha;
			}
			if( _blendMode < 0 ){
				$target.blendMode = blendMode;
			}
			if( _materialLibrary < 0 ){
				for( key in materialLibrary ){
					$target.materialLibrary.getMaterial( key ).material = TAF.SELF.materialGet( materialLibrary[key] );
				}
			}else if( _material < 0 ){
				$target.material = TAF.SELF.materialGet( material );
			}
			
			if( _back < 0 ){
				$target.back = TAF.SELF.materialGet( back );
			}
			if( _autoSize < 0 ){
				if( 'bitmap' in $target.material ){
					$target.width = $target.material.bitmap.width;
					$target.height = $target.material.bitmap.height;
				}
			}
			if( _blur < 0 ){
				temp = filterSet( $target, 'blur' );
				temp.blurX = blurX;
				temp.blurY = blurY;
				temp.quality = blurQ;
				isFilter = -1;
			}
			if( _glow < 0 ){
				temp = filterSet( $target, 'glow' );
				temp.blurX = glowX;
				temp.blurY = glowY;
				temp.quality = glowQ;
				temp.strength = glowS;
				temp.alpha = glowA;
				temp.color = glowC;
				isFilter = -1;
			}
			if( _drop < 0 ){
				temp = filterSet( $target, 'drop' );
				temp.color = dropC;
				temp.blurX = dropX;
				temp.blurY = dropY;
				temp.quality = dropQ;
				temp.angle = dropAN;
				temp.alpha = dropA;
				temp.distance = dropD;
				isFilter = -1;
			}
			if( _blurRemove < 0 ){
				filterRemove( $target, 'blur' );
				isFilter = -1;
			}
			if( _glowRemove < 0 ){
				filterRemove( $target, 'glow' );
				isFilter = -1;
			}
			if( _dropRemove < 0 ){
				filterRemove( $target, 'drop' );
				isFilter = -1;
			}
			if( isFilter < 0 ){
				temp = TAF.SELF._treeFilter[$target];
				if( temp && temp.length ){
					$target.filters = temp;
				}else{
					$target.filters = null;
				}
			}
		}
		private function operation( $key:String, $operation:String, $var:TAFawayVar, $target:* ):void{
			var temp:Number;
			if( $target is Number ){
				switch( $operation ){
				case'': temp = $target; break;
				case'+': temp = $var[$key] + $target; break;
				case'-': temp = $var[$key] - $target; break;
				}
			}else{
				switch( $operation ){
				case'': temp = $target[$key]; break;
				case'+': temp = $var[$key] + $target[$key]; break;
				case'-': temp = $var[$key] - $target[$key]; break;
				}
			}
			this['_' + $key] = -1;
			this[$key] = temp;
		}
		internal function initFromVar( $var:TAFawayVar = null, $target:* = null, $operation:String = '' ):TAFawayVar{
			var key:*;
			if( $var === null ){
				$var = this;
			}
			if( $target === null ){
				$target = $var;
			}
			if( $var._x < 0 ){
				operation( 'x', $operation, $var, $target );
			}
			if( $var._y < 0 ){
				operation( 'y', $operation, $var, $target );
			}
			if( $var._z < 0 ){
				operation( 'z', $operation, $var, $target );
			}
			if( $var._rotationX < 0 ){
				operation( 'rotationX', $operation, $var, $target );
			}
			if( $var._rotationY < 0 ){
				operation( 'rotationY', $operation, $var, $target );
			}
			if( $var._rotationZ < 0 ){
				operation( 'rotationZ', $operation, $var, $target );
			}
			if( $var._rotation < 0 ){
				operation( 'rotation', $operation, $var, $target );
			}
			if( $var._scaling < 0 ){
				operation( 'scaling', $operation, $var, $target );
			}
			if( $var._scaleX < 0 ){
				operation( 'scaleX', $operation, $var, $target );
			}
			if( $var._scaleY < 0 ){
				operation( 'scaleY', $operation, $var, $target );
			}
			if( $var._scaleZ < 0 ){
				operation( 'scaleZ', $operation, $var, $target );
			}
			if( $var._width < 0 ){
				operation( 'width', $operation, $var, $target );
			}
			if( $var._height < 0 ){
				operation( 'height', $operation, $var, $target );
			}
			if( $var._depth < 0 ){
				operation( 'depth', $operation, $var, $target );
			}
			if( $var._segmentsW < 0 ){
				operation( 'segmentsW', $operation, $var, $target );
			}
			if( $var._segmentsH < 0 ){
				operation( 'segmentsH', $operation, $var, $target );
			}
			if( $var._alpha < 0 ){
				operation( 'alpha', $operation, $var, $target );
			}
			
			if( $var._ownCanvas < 0 ){
				_ownCanvas = -1;
				ownCanvas = $target.ownCanvas;
			}
			if( $var._ownLights < 0 ){
				_ownLights = -1;
				ownLights = $target.ownLights;
			}
			if( $var._visible < 0 ){
				_visible = -1;
				visible = $target.visible;
			}
			if( $var._depth < 0 ){
				_depth = -1;
				depth = $target.depth;
			}
			if( $var._bothsides < 0 ){
				_bothsides = -1;
				bothsides = $target.bothsides;
			}
			if( $var._mouseEnabled < 0 ){
				_mouseEnabled = -1;
				mouseEnabled = $target.mouseEnabled;
			}
			
			if( $var._blendMode < 0 ){
				_blendMode = -1;
				blendMode = $target.blendMode;
			}
			
			if( $var._material < 0 ){
				_material = -1;
				material = $target.material;
			}
			if( $var._back < 0 ){
				_back = -1;
				back = $target.back;
			}
			return this;
		}
		private function filterRemove( $target:*, $filter:String ):void{
			var key:*, temp:Array;
			temp = TAF.SELF._treeFilter[$target];
			if( temp ){
				for( key in temp ){
					switch( $filter ){
					case'blur':
						if( temp[key] is BlurFilter ){
							TAF.SELF.poolCollectBlurFilter( temp[key] );
							temp.splice( key, 1 );
							return;
						}
						break;
					case'glow':
						if( temp[key] is GlowFilter ){
							TAF.SELF.poolCollectGlowFilter( temp[key] );
							temp.splice( key, 1 );
							return;
						}
						break;
					}
				}
			}
		}
		private function filterSet( $target:*, $filter:String ):*{
			var key:*, temp:Array;
			temp = TAF.SELF._treeFilter[$target]; 
			if( temp ){}else{
				TAF.SELF._treeFilter[$target] = temp = [];
			}
			for each( key in temp ){
				switch( $filter ){
				case'blur':
					if( key is BlurFilter ){
						return key;
					}
					break;
				case'glow':
					if( key is GlowFilter ){
						return key;
					}
					break;
				case'drop':
					if( key is DropShadowFilter ){
						return key;
					}
					break;
				}
			}
			switch( $filter ){
			case'blur':
				key = TAF.SELF.poolPullBlurFilter();
				break;
			case'glow':
				key = TAF.SELF.poolPullGlowFilter();
				break;
			case'drop':
				key = TAF.SELF.poolPullDropFilter();
				break;
			}
			temp[temp.length] = key; 
			return key;
		}
	}
}